mysql的前缀匹配 + 联合索引优化

面试官您好,关于“时空衣橱”模块中的关键词搜索优化,我确实做了基于 MySQL 的前缀匹配 + 联合索引 这一块优化处理,主要是为了解决模糊搜索性能差的问题。

✅ 背景问题:

在最初实现时,我使用的是 LIKE '%关键词%' 来做模糊搜索,但这种写法在 MySQL 中是无法命中索引的,查询时会进行全表扫描。数据量一旦多了,查询速度就明显变慢,页面响应卡顿。


✅ 解决思路:改为前缀匹配 + 联合索引

为了提高性能,我做了如下几步优化:

1️⃣ 改写查询语句

一开始我用的是 LIKE '%关键词%' 来做模糊匹配,但这种写法 MySQL 是无法用上索引的,只能全表扫描,查询一多就很慢。

后来我改成了 LIKE '关键词%',也就是前缀匹配,这样就能利用 MySQL B+ 树索引的有序性,大大加快搜索效率。

2️⃣ 字段设计上,做了联合索引

在服饰表里,我们有字段比如 name(服饰名称)、tags(标签)、category(类别)。

我根据搜索习惯设计了类似 (category, name)(tags, name) 的联合索引。

比如用户选了“裙子”类别再搜关键词,这时就能利用 category 作为联合索引的前缀,直接命中索引查到 name 字段,避免回表查询。

这里有个细节:联合索引字段的顺序非常关键,必须遵循“最左前缀原则”,我把筛选条件更常用的字段放前面,提升命中率。

3️⃣ 使用 EXPLAIN 验证执行计划

我通过 EXPLAIN 查看执行计划,确认是否真正用了索引。

优化前是 type: ALL(全表扫描),优化后变成了 rangeref,说明走了索引路径,性能提升非常明显。

这套优化下来,在不引入 Elasticsearch 这种搜索引擎的前提下,就把原本几百毫秒的查询延迟降到了几十毫秒,用户体验改善还是比较明显的。


✅ 扩展策略:保留模糊搜索体验的同时兼顾性能

当然前缀匹配的体验不如全文搜索灵活,所以我也做了一个折中方案:

  • 当用户输入两个字以上时使用前缀匹配;
  • 输入特别短或模糊性很强时,系统默认推荐热门关键词;
  • 后期我们也调研了接入 全文索引(FULLTEXT)Elasticsearch 来支持复杂搜索,目前项目数据量还未到那个规模,所以暂未采用。

✅ 总结:

通过前缀匹配 + 联合索引的优化方式,在不接入额外搜索引擎的情况下,实现了搜索性能的大幅提升,查询平均延迟从几百毫秒降到几十毫秒,配合 Redis 缓存之后基本可以秒级响应,满足当前的实际业务场景。